home *** CD-ROM | disk | FTP | other *** search
/ BCI NET / BCI NET Dec 94.iso / archives / programming / languages / ami_nuweb0.87c.lha / latex.c < prev    next >
Encoding:
C/C++ Source or Header  |  1994-10-12  |  15.7 KB  |  405 lines

  1. #include "global.h"
  2. static void copy_scrap(FILE *);
  3.   /* formats the body of a scrap */
  4. static void print_scrap_numbers(FILE *, Scrap_Node *);
  5.   /* formats a list of scrap numbers */
  6. static void format_entry(Name *, FILE *, int);
  7.   /* formats an index entry */
  8. static void format_user_entry(Name *, FILE *);
  9. void write_tex(char *file_name, char *tex_name)
  10. {
  11.   FILE *tex_file = fopen(tex_name, "w");
  12.   if (tex_file) {
  13.     if (verbose_flag)
  14. #ifdef _AMIGA
  15.       fprintf(stderr, get_string(MSG_VERBOSE_17A), tex_name);
  16. #else
  17.       fprintf(stderr, "writing %s\n", tex_name);
  18. #endif
  19.     source_open(file_name);
  20.     {
  21.       int scraps = 1;
  22.       int c = source_get();
  23.       while (c != EOF) {
  24.         if (c == '@')
  25.           {
  26.             int big_definition = FALSE;
  27.             c = source_get();
  28.             switch (c) {
  29.               case 'O': big_definition = TRUE;
  30.               case 'o': {
  31.                           Name *name = collect_file_name();
  32.                           {
  33.                             fputs("\\begin{flushleft} \\small", tex_file);
  34.                             if (!big_definition)
  35.                               fputs("\n\\begin{minipage}{\\linewidth}", tex_file);
  36.                             fprintf(tex_file, " \\label{scrap%d}\n", scraps);
  37.                           }
  38.                           fprintf(tex_file, "\\verb@\"%s\"@ {\\footnotesize ", name->spelling);
  39.                           write_single_scrap_ref(tex_file, scraps++);
  40.                           fputs(" }${}\\equiv{}$\n", tex_file);
  41.                           {
  42.                             fputs("\\vspace{-1ex}\n\\begin{list}{}{} \\item\n", tex_file);
  43.                             copy_scrap(tex_file);
  44.                             fputs("$\\Diamond$\n\\end{list}\n", tex_file);
  45.                           }
  46.                           {
  47.                             if (name->defs->next) {
  48.                               fputs("\\vspace{-1ex}\n", tex_file);
  49.                               fputs("\\footnotesize\\addtolength{\\baselineskip}{-1ex}\n", tex_file);
  50.                               fputs("\\begin{list}{}{\\setlength{\\itemsep}{-\\parsep}", tex_file);
  51.                               fputs("\\setlength{\\itemindent}{-\\leftmargin}}\n", tex_file);
  52.                           #ifdef _AMIGA
  53.                               fputs(get_string(MSG_LATEX_20B), tex_file);
  54.                           #else
  55.                               fputs("\\item File defined by scraps ", tex_file);
  56.                           #endif
  57.                               print_scrap_numbers(tex_file, name->defs);
  58.                               fputs("\\end{list}\n", tex_file);
  59.                             }
  60.                             else
  61.                               fputs("\\vspace{-2ex}\n", tex_file);
  62.                           }
  63.                           {
  64.                             if (!big_definition)
  65.                               fputs("\\end{minipage}\\\\[4ex]\n", tex_file);
  66.                             fputs("\\end{flushleft}\n", tex_file);
  67.                             do
  68.                               c = source_get();
  69.                             while (isspace(c));
  70.                           }
  71.                         }
  72.                         break;
  73.               case 'D': big_definition = TRUE;
  74.               case 'd': {
  75.                           Name *name = collect_macro_name();
  76.                           {
  77.                             fputs("\\begin{flushleft} \\small", tex_file);
  78.                             if (!big_definition)
  79.                               fputs("\n\\begin{minipage}{\\linewidth}", tex_file);
  80.                             fprintf(tex_file, " \\label{scrap%d}\n", scraps);
  81.                           }
  82.                           fprintf(tex_file, "${}\\langle{}$%s {\\footnotesize ", name->spelling);
  83.                           write_single_scrap_ref(tex_file, scraps++);
  84.                           fputs("}${}\\rangle{}\\equiv{}$\n", tex_file);
  85.                           {
  86.                             fputs("\\vspace{-1ex}\n\\begin{list}{}{} \\item\n", tex_file);
  87.                             copy_scrap(tex_file);
  88.                             fputs("$\\Diamond$\n\\end{list}\n", tex_file);
  89.                           }
  90.                           {
  91.                             fputs("\\vspace{-1ex}\n", tex_file);
  92.                             fputs("\\footnotesize\\addtolength{\\baselineskip}{-1ex}\n", tex_file);
  93.                             fputs("\\begin{list}{}{\\setlength{\\itemsep}{-\\parsep}", tex_file);
  94.                             fputs("\\setlength{\\itemindent}{-\\leftmargin}}\n", tex_file);
  95.                             if (name->defs->next) {
  96.                           #ifdef _AMIGA
  97.                               fputs(get_string(MSG_LATEX_20C), tex_file);
  98.                           #else
  99.                               fputs("\\item Macro defined by scraps ", tex_file);
  100.                           #endif
  101.                               print_scrap_numbers(tex_file, name->defs);
  102.                             }
  103.                           }
  104.                           {
  105.                             if (name->uses) {
  106.                               if (name->uses->next) {
  107.                           #ifdef _AMIGA
  108.                                 fputs(get_string(MSG_LATEX_21A1), tex_file);
  109.                           #else
  110.                                 fputs("\\item Macro referenced in scraps ", tex_file);
  111.                           #endif
  112.                                 print_scrap_numbers(tex_file, name->uses);
  113.                               }
  114.                               else {
  115.                           #ifdef _AMIGA
  116.                                 fputs(get_string(MSG_LATEX_21A2), tex_file);
  117.                           #else
  118.                                 fputs("\\item Macro referenced in scrap ", tex_file);
  119.                           #endif
  120.                                 write_single_scrap_ref(tex_file, name->uses->scrap);
  121.                                 fputs(".\n", tex_file);
  122.                               }
  123.                             }
  124.                             else {
  125.                           #ifdef _AMIGA
  126.                               fputs(get_string(MSG_LATEX_21A3), tex_file);
  127.                               fprintf(stderr, get_string(MSG_WARNING_21A),
  128.                           #else
  129.                               fputs("\\item Macro never referenced.\n", tex_file);
  130.                               fprintf(stderr, "%s: <%s> never referenced.\n",
  131.                           #endif
  132.                                       command_name, name->spelling);
  133.                             }
  134.                             fputs("\\end{list}\n", tex_file);
  135.                           }
  136.                           {
  137.                             if (!big_definition)
  138.                               fputs("\\end{minipage}\\\\[4ex]\n", tex_file);
  139.                             fputs("\\end{flushleft}\n", tex_file);
  140.                             do
  141.                               c = source_get();
  142.                             while (isspace(c));
  143.                           }
  144.                         }
  145.                         break;
  146.               case 'f': {
  147.                           if (file_names) {
  148.                             fputs("\n{\\small\\begin{list}{}{\\setlength{\\itemsep}{-\\parsep}",
  149.                                   tex_file);
  150.                             fputs("\\setlength{\\itemindent}{-\\leftmargin}}\n", tex_file);
  151.                             format_entry(file_names, tex_file, TRUE);
  152.                             fputs("\\end{list}}", tex_file);
  153.                           }
  154.                           c = source_get();
  155.                         }
  156.                         break;
  157.               case 'm': {
  158.                           if (macro_names) {
  159.                             fputs("\n{\\small\\begin{list}{}{\\setlength{\\itemsep}{-\\parsep}",
  160.                                   tex_file);
  161.                             fputs("\\setlength{\\itemindent}{-\\leftmargin}}\n", tex_file);
  162.                             format_entry(macro_names, tex_file, FALSE);
  163.                             fputs("\\end{list}}", tex_file);
  164.                           }
  165.                           c = source_get();
  166.                         }
  167.                         break;
  168.               case 'u': {
  169.                           if (user_names) {
  170.                             fputs("\n{\\small\\begin{list}{}{\\setlength{\\itemsep}{-\\parsep}",
  171.                                   tex_file);
  172.                             fputs("\\setlength{\\itemindent}{-\\leftmargin}}\n", tex_file);
  173.                             format_user_entry(user_names, tex_file);
  174.                             fputs("\\end{list}}", tex_file);
  175.                           }
  176.                           c = source_get();
  177.                         }
  178.                         break;
  179.               case '@': putc(c, tex_file);
  180.               default:  c = source_get();
  181.                         break;
  182.             }
  183.           }
  184.         else {
  185.           putc(c, tex_file);
  186.           c = source_get();
  187.         }
  188.       }
  189.     }
  190.     fclose(tex_file);
  191.   }
  192.   else
  193. #ifdef _AMIGA
  194.     fprintf(stderr, get_string(MSG_WARNING_17A), command_name, tex_name);
  195. #else
  196.     fprintf(stderr, "%s: can't open %s\n", command_name, tex_name);
  197. #endif
  198. } static void print_scrap_numbers(FILE *tex_file, Scrap_Node *scraps)
  199. {
  200.   int page;
  201.   write_scrap_ref(tex_file, scraps->scrap, TRUE, &page);
  202.   scraps = scraps->next;
  203.   while (scraps) {
  204.     write_scrap_ref(tex_file, scraps->scrap, FALSE, &page);
  205.     scraps = scraps->next;
  206.   }
  207.   fputs(".\n", tex_file);
  208. } static void copy_scrap(FILE *file)
  209. {
  210.   int indent = 0;
  211.   int c = source_get();
  212.   fputs("\\mbox{}\\verb@", file);
  213.   while (1) {
  214.     switch (c) {
  215.       case '@':  {
  216.                    c = source_get();
  217.                    switch (c) {
  218.                      case '@': fputs("@{\\tt @}\\verb@", file);
  219.                                break;
  220.                      case '|': {
  221.                                  do {
  222.                                    do
  223.                                      c = source_get();
  224.                                    while (c != '@');
  225.                                    c = source_get();
  226.                                  } while (c != '}');
  227.                                }
  228.                      case '}': putc('@', file);
  229.                                return;
  230.                      case '<': {
  231.                                  Name *name = collect_scrap_name();
  232.                                  fprintf(file, "@${}\\langle{}$%s {\\footnotesize ", name->spelling);
  233.                                  if (name->defs)
  234.                                    {
  235.                                      Scrap_Node *p = name->defs;
  236.                                      write_single_scrap_ref(file, p->scrap);
  237.                                      p = p->next;
  238.                                      if (p)
  239.                                        fputs(", \\ldots\\ ", file);
  240.                                    }
  241.                                  else {
  242.                                    putc('?', file);
  243.                                #ifdef _AMIGA
  244.                                    fprintf(stderr, get_string(MSG_WARNING_23B),
  245.                                #else
  246.                                    fprintf(stderr, "%s: scrap never defined <%s>\n",
  247.                                #endif
  248.                                            command_name, name->spelling);
  249.                                  }
  250.                                  fputs("}${}\\rangle{}$\\verb@", file);
  251.                                }
  252.                                break;
  253.                      default:  /* ignore these since pass1 will have warned about them */
  254.                                break;
  255.                    }
  256.                  }
  257.                  break;
  258.       case '\n': fputs("@\\\\\n\\mbox{}\\verb@", file);
  259.                  indent = 0;
  260.                  break;
  261.       case '\t': {
  262.                    int delta = 8 - (indent % 8);
  263.                    indent += delta;
  264.                    while (delta > 0) {
  265.                      putc(' ', file);
  266.                      delta--;
  267.                    }
  268.                  }
  269.                  break;
  270.       default:   putc(c, file);
  271.                  indent++;
  272.                  break;
  273.     }
  274.     c = source_get();
  275.   }
  276. } static void format_entry(Name *name, FILE *tex_file, int file_flag)
  277. {
  278.   while (name) {
  279.     format_entry(name->llink, tex_file, file_flag);
  280.     {
  281.       fputs("\\item ", tex_file);
  282.       if (file_flag) {
  283.         fprintf(tex_file, "\\verb@\"%s\"@ ", name->spelling);
  284.         {
  285.           Scrap_Node *p = name->defs;
  286.         #ifdef _AMIGA
  287.           if (p->next) {
  288.             fputs(get_string(MSG_LATEX_25A1), tex_file);
  289.             print_scrap_numbers(tex_file, p);
  290.           }
  291.           else {
  292.             fputs(get_string(MSG_LATEX_25A2), tex_file);
  293.         #else
  294.           fputs("{\\footnotesize Defined by scrap", tex_file);
  295.           if (p->next) {
  296.             fputs("s ", tex_file);
  297.             print_scrap_numbers(tex_file, p);
  298.           }
  299.           else {
  300.             putc(' ', tex_file);
  301.         #endif
  302.             write_single_scrap_ref(tex_file, p->scrap);
  303.             putc('.', tex_file);
  304.           }
  305.           putc('}', tex_file);
  306.         }
  307.       }
  308.       else {
  309.         fprintf(tex_file, "${}\\langle{}$%s {\\footnotesize ", name->spelling);
  310.         {
  311.           Scrap_Node *p = name->defs;
  312.           if (p) {
  313.             int page;
  314.             write_scrap_ref(tex_file, p->scrap, TRUE, &page);
  315.             p = p->next;
  316.             while (p) {
  317.               write_scrap_ref(tex_file, p->scrap, FALSE, &page);
  318.               p = p->next;
  319.             }
  320.           }
  321.           else
  322.             putc('?', tex_file);
  323.         }
  324.         fputs("}${}\\rangle{}$ ", tex_file);
  325.         {
  326.           Scrap_Node *p = name->uses;
  327.           fputs("{\\footnotesize ", tex_file);
  328.           if (p) {
  329.         #ifdef _AMIGA
  330.             if (p->next) {
  331.               fputs(get_string(MSG_LATEX_25C1), tex_file);
  332.               print_scrap_numbers(tex_file, p);
  333.             }
  334.             else {
  335.               fputs(get_string(MSG_LATEX_25C2), tex_file);
  336.         #else
  337.             fputs("Referenced in scrap", tex_file);
  338.             if (p->next) {
  339.               fputs("s ", tex_file);
  340.               print_scrap_numbers(tex_file, p);
  341.             }
  342.             else {
  343.               putc(' ', tex_file);
  344.         #endif
  345.               write_single_scrap_ref(tex_file, p->scrap);
  346.               putc('.', tex_file);
  347.             }
  348.           }
  349.           else
  350.         #ifdef _AMIGA
  351.             fputs(get_string(MSG_LATEX_25C3), tex_file);
  352.         #else
  353.             fputs("Not referenced.", tex_file);
  354.         #endif
  355.           putc('}', tex_file);
  356.         }
  357.       }
  358.       putc('\n', tex_file);
  359.     }
  360.     name = name->rlink;
  361.   }
  362. } static void format_user_entry(Name *name, FILE *tex_file)
  363. {
  364.   while (name) {
  365.     format_user_entry(name->llink, tex_file);
  366.     {
  367.       Scrap_Node *uses = name->uses;
  368.       if (uses) {
  369.         int page;
  370.         Scrap_Node *defs = name->defs;
  371.         fprintf(tex_file, "\\item \\verb@%s@: ", name->spelling);
  372.         if (uses->scrap < defs->scrap) {
  373.           write_scrap_ref(tex_file, uses->scrap, TRUE, &page);
  374.           uses = uses->next;
  375.         }
  376.         else {
  377.           if (defs->scrap == uses->scrap)
  378.             uses = uses->next;
  379.           fputs("\\underline{", tex_file);
  380.           write_single_scrap_ref(tex_file, defs->scrap);
  381.           putc('}', tex_file);
  382.           page = -2;
  383.           defs = defs->next;
  384.         }
  385.         while (uses || defs) {
  386.           if (uses && (!defs || uses->scrap < defs->scrap)) {
  387.             write_scrap_ref(tex_file, uses->scrap, FALSE, &page);
  388.             uses = uses->next;
  389.           }
  390.           else {
  391.             if (uses && defs->scrap == uses->scrap)
  392.               uses = uses->next;
  393.             fputs(", \\underline{", tex_file);
  394.             write_single_scrap_ref(tex_file, defs->scrap);
  395.             putc('}', tex_file);
  396.             page = -2;
  397.             defs = defs->next;
  398.           }
  399.         }
  400.         fputs(".\n", tex_file);
  401.       }
  402.     }
  403.     name = name->rlink;
  404.   }